/*
 * To change this license header, choose License Headers in Project Properties.
 * To change this template file, choose Tools | Templates
 * and open the template in the editor.
 */
package com.synjones.zeuscloudapp.service;

import com.alibaba.fastjson.JSON;
import com.google.gson.Gson;
import com.synjones.zeus.model.StatusInfo;
import com.synjones.zeuscloudapp.bean.CodeDescPair;
import com.synjones.zeuscloudapp.util.DataPack;
import com.synjones.zeuscloudapp.util.ReqBean;
import com.synjones.zeuscloudapp.util.StatusEnum;
import com.synjones.zeus.model.ExReqBean;
import com.synjones.zeus.model.ExRespBean;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;

import javax.servlet.http.HttpServletRequest;

/**
 * @param <T>
 * @param <E>
 * @param <R>
 * @param <A>
 * @author tnnan
 */
@Component
public abstract class AbstractDataPackServiceImpl<T, E, R, A> extends AbstractCommonServiceImpl<T, A> {

    private final Logger logger = LoggerFactory.getLogger(getClass());

    /**
     * 获取request中内容后格式化
     *
     * @param reqBean HttpServletRequest
     * @return ExReqBean<E>
     * @author yys
     * Description: 获取request中内容后格式化
     * @date 14:46 2018-03-15
     */
    public abstract ExReqBean<E> buildReqBean(ReqBean<T> reqBean);

    public CodeDescPair verifyData(ReqBean<T> reqBean) {
        //null表示验证通过
        return null;
    }

    /**
     * 去eureka服务找到对应服务获取数据后格式化
     *
     * @param reqBean HttpServletRequest
     * @return ExReqBean<E>
     * @author yys
     * Description: 去eureka服务找到对应服务获取数据后格式化
     * @date 14:49 2018-03-15
     */
    public abstract ExRespBean<R> eureka(ExReqBean<E> reqBean);

    /**
     * HttpServletResponse resBean中内容后格式化
     *
     * @param resBean HttpServletResponse
     * @return ExReqBean<E>
     * @author yys
     * Description: HttpServletResponse resBean中内容后格式化
     * @date 14:54 2018-03-15
     */
    public abstract A buildResBean(ExRespBean<R> resBean);

    public DataPack<A> build(ExRespBean<R> resBean) {
        return resBean.statusOk() ? new DataPack(this.buildResBean(resBean))
                : new DataPack(false, resBean.getTipMsg());
    }

    @Override
    public DataPack<A> buildDataPack(HttpServletRequest request) {
        ExRespBean<R> eureka;
        try {
            ReqBean<T> reqBean = this.getReqBean(request);
            CodeDescPair verifyData = this.verifyData(reqBean);
            if (verifyData != null) {
                logger.info("数据验证失败");
                return new DataPack(false, verifyData.getDesc(), StatusInfo._10000.desc());
            }
            ExReqBean<E> buildReqBean = this.buildReqBean(reqBean);
            logger.info("eureka服务请求参数为{}", getShortLogString(JSON.toJSONString(buildReqBean)));
            eureka = eureka(buildReqBean);
            logger.info("eureka服务返回的数据为{}", getShortLogString(JSON.toJSONString(eureka)));
        } catch (Exception e) {
            logger.error("请求eureka服务异常{}", e);
            return new DataPack(false, StatusEnum.TIMEOUT_ERROR.getMessage());
        }
        return this.build(eureka);
    }

    private String getShortLogString(String log) {
        if (log != null && log.length() > 2000) {
            return log.substring(0, 1999);
        }
        return log;
    }
}
